\NeedsTeXFormat{LaTeX2e}
\ProvidesPackage{stb-brackets}[2019/03/09]

\RequirePackage{etoolbox}
\RequirePackage{mathtools} % Lots of math stuff
\RequirePackage{scalerel} % For scaling bags
\RequirePackage{stmaryrd} % For double brackets and bags
\RequirePackage{xparse}

% --- Delimiter for set-builder notation  ---
\newcommand*{\@setbuildermid}{:}
\DeclareOption{setbar}{
    \renewcommand*{\@setbuildermid}{\:\delimsize\vert\:}
}
\DeclareOption{setcolon}{
    \renewcommand*{\@setbuildermid}{:}
}

% --- Notation for expression evaluation ---
\newcommand*{\@evalleftdelim}{.}
\newcommand*{\@evalbar}{\rvert}
\newcommand*{\@evalrightdelim}{.}
\DeclareOption{evalbar}{
    \renewcommand*{\@evalleftdelim}{.}
    \renewcommand*{\@evalbar}{\rvert}
    \renewcommand*{\@evalrightdelim}{.}
}
\DeclareOption{evalbrackets}{
    \renewcommand*{\@evalleftdelim}{\lbrack}
    \renewcommand*{\@evalbar}{\rbrack}
    \renewcommand*{\@evalrightdelim}{.}
}

\ProcessOptions\relax

% --- Brackets ---
% Helper macro -- adapted from Sebastien Gouezel's code on pg. 29 of the mathtools doumentation
\newcommand{\@MTkillspecial}[1]{
    \bgroup
    \catcode`\&=9
    \let\\\relax%
    \scantokens{#1}%
    \egroup
}

% Constructor
\NewDocumentCommand{\DeclareSplittableBrackets}{m m m}{%
    \DeclarePairedDelimiter{#1}{#2}{#3}
    \reDeclarePairedDelimiterInnerWrapper{#1}{star}{
        \mathopen{##1\vphantom{\@MTkillspecial{##2}}\kern-\nulldelimiterspace\right.}
        ##2
        \mathclose{\left.\kern-\nulldelimiterspace\vphantom{\@MTkillspecial{##2}}##3}
    }
}

% Common brackets
\AfterEndPreamble{ % Delay this to override unicode-math's override
    \undef\angles
    \DeclareSplittableBrackets{\angles}{\langle}{\rangle}
}
\DeclareSplittableBrackets{\bars}{\lvert}{\rvert}
\DeclareSplittableBrackets{\braces}{\lbrace}{\rbrace}
\DeclareSplittableBrackets{\brackets}{\lbrack}{\rbrack}
\DeclareSplittableBrackets{\ceil}{\lceil}{\rceil}
\DeclareSplittableBrackets{\dbars}{\lVert}{\rVert}
\DeclareSplittableBrackets{\dbrackets}{\llbracket}{\rrbracket}
\DeclareSplittableBrackets{\floor}{\lfloor}{\rfloor}
\DeclareSplittableBrackets{\parens}{\lparen}{\rparen}

\let\abs\bars
\let\set\braces

% Scalable bags
\NewDocumentCommand{\bags}{s o m}{%
    \IfBooleanTF{#1}
        {\scaleleftright{\lbag}{#3}{\rbag}}
        {{#2 \lbag} #3 {#2 \rbag}}
}

% --- Set-builder notation ---
\DeclarePairedDelimiterX{\setbuilder}[2]{\lbrace}{\rbrace}{#1 \@setbuildermid \mathopen{} #2}

% --- Functions ---
\DeclarePairedDelimiterXPP{\apply}[2]{#1}{\lparen}{\rparen}{}{#2}
\DeclarePairedDelimiterXPP{\applyy}[3]{#1}{\lparen}{\rparen}{}{#2 \delimsize\rparen \delimsize\lparen #3}
\DeclarePairedDelimiterXPP{\applyyy}[4]{#1}{\lparen}{\rparen}{}{#2 \delimsize\rparen \delimsize\lparen #3 \delimsize\rparen \delimsize\lparen #4}

\DeclarePairedDelimiterXPP{\bapply}[2]{#1}{\lbrack}{\rbrack}{}{#2}

\DeclarePairedDelimiterXPP{\restrict}[2]{}{.}{\rvert}{_{#2}}{#1}
\DeclarePairedDelimiterXPP{\evalat}[2]{}{\@evalleftdelim}{\@evalbar}{_{#2}}{#1 \delimsize\@evalrightdelim}

\endinput